package com.acme.bankapp.domain.bank;

import java.util.Date;

import com.acme.bankapp.exceptions.bank.*;
import com.acme.bankapp.listeners.bank.*;

/**
 * Class stores clients of the bank
 * @author alex
 */
public class Bank {
	private Client[] clients;
	private int clientsCount;
	private static final int CLIENTS_MAX = 10;
	
	private ClientRegistrationListener[] listeners;
	private int listenersCount;
	private static final int LISTENERS_MAX = 10;
	
	/**
	 * The default constructor
	 * @throws ListenersMaxException 
	 */
	public Bank() throws ListenersMaxException {
		this.clients = new Client[Bank.CLIENTS_MAX];
		this.listeners = new ClientRegistrationListener[Bank.LISTENERS_MAX];
		
		this.addListener(new ClientRegistrationListener() {
			public void onClientAdded(Client client) {
				System.out.println(client.getName() + " " + new Date());
			}
		});
	}
	
	/**
	 * @param id the client id
	 * @return the client
	 */
	public Client getClient(int id) {
		if (id >= 0 && id <= this.clientsCount) {
			return this.clients[id];
		} else {
			return null;
		}
	}
	
	/**
	 * @param name the client name
	 * @return the client
	 */
	public Client getClient(String name) {
		for (int i = 0; i < this.clientsCount; i++) {
			if(this.clients[i].getName() == name) {
				return this.clients[i];
			}
		}
		return null;
	}
	
	/**
	 * Adds the client to bank, does not allows to add a client with empty name
	 * @param client the client
	 * @throws ClientsMaxException 
	 * @throws ClientExistsException 
	 */
	public void addClient(Client client) throws ClientsMaxException, ClientExistsException {
		if (this.clientsCount < Bank.CLIENTS_MAX) {
			if (this.getClient(client.getName()) == null) {
				this.clients[this.clientsCount++] = client;
				this.runListeners(client);
			} else {
				throw new ClientExistsException();
			}
		} else {
			throw new ClientsMaxException();
		}
	}
	
	/**
	 * @return the clients count
	 */
	public int getClientsCount() {
		return this.clientsCount;
	}
	
	/**
	 * @param listener the registration listener
	 * @throws ListenersMaxException 
	 */
	public void addListener(ClientRegistrationListener listener) throws ListenersMaxException {
		if (this.listenersCount < Bank.LISTENERS_MAX) {
			this.listeners[this.listenersCount++] = listener;
		} else {
			throw new ListenersMaxException();
		}
	}
	
	/**
	 * Method iterates and runs listeners
	 * @param client the client
	 */
	public void runListeners(Client client) {
		for (int i = 0; i < this.listenersCount; i++) {
			this.listeners[i].onClientAdded(client);
		}
	}
}
